<template>
  <!-- 费用信息 -->
  <view class="fee-info" v-if="feeTabs.length">
    <view class="fee-info-header">
      <ve-subsection
        :style="{ width: feeTabs.length > 1 ? '352rpx' : '180rpx' }"
        v-if="feeTabs.length"
        :current="feeTabIndex"
        activeColor="#3072F6"
        bgColor="#F7F8FA"
        height="72"
        inactiveColor="#55585F"
        :list="feeTabs"
        @change="onFeeTabChange"
      />
      <!-- 租车费用的全选 -->
      <customCheck
        v-if="currSelTabVal == 0"
        v-model="rentalChecked"
        v-model:indeterminate="rentalIndeterminate"
        class="check-box"
        renderType="square"
        @change="onAllCheckedChange"
        >全选</customCheck
      >
      <!-- 违章费用的全选 -->
      <customCheck
        v-if="currSelTabVal == 1"
        v-model="violationChecked"
        v-model:indeterminate="violationIndeterminate"
        class="check-box"
        renderType="square"
        @change="onAllCheckedChange"
        >全选</customCheck
      >
    </view>
    <view class="fee-info-content">
      <!-- 租车费用 -->
      <block v-if="feeTabs[feeTabIndex].value == 0">
        <rentalList v-if="orderFeeList && orderFeeList.length" :feeList="orderFeeList" @change="onRentalCheckChange" />
        <ve-empty v-else />
      </block>
      <!-- 违章费用 -->
      <block v-if="feeTabs[feeTabIndex].value == 1">
        <violationList
          v-if="violationFeeList && violationFeeList.length"
          :feeList="violationFeeList"
          @change="onViolationListCheckChange"
        />
        <ve-empty v-else />
      </block>
    </view>
  </view>
</template>
<script setup>
  import { ref, computed, nextTick } from 'vue'
  import { getOrderFeeList, getViolationFeeList } from '@/api/order/sOrder'
  import customCheck from './custom-check.vue'
  import { decimalAddition } from '@/utils/index'

  // 租车费用
  import rentalList from './rental-list.vue'
  // 违章费用
  import violationList from './violation-list.vue'

  const props = defineProps({
    // 押金抵扣详情
    depositDetail: Object,
    // 抵扣合计
    deductionSum: Number,
  })

  // 租车费用选中 | 半选
  const rentalChecked = ref(false)
  const rentalIndeterminate = ref(false)
  // 违章费用选中 | 半选
  const violationChecked = ref(false)
  const violationIndeterminate = ref(false)

  const emits = defineEmits(['update:orderFeeList', 'update:violationFeeList', 'change'])

  // 费用信息选中下标
  const feeTabIndex = ref(-1)
  // 费用信息
  const feeTabs = ref([])

  // 当前选中的tab的value
  const currSelTabVal = computed(() => {
    const sleTab = feeTabs.value[feeTabIndex.value]
    return sleTab && sleTab.value
  })

  // 分段器切换
  const onFeeTabChange = (index) => {
    feeTabIndex.value = index

    // 查询数据
    fetchData()
  }

  // 父组件选择了押金抵扣类型
  const compareType = (newOptions) => {
    // 新的types
    const newTabs = newOptions.map((item) => {
      return {
        name: item.label,
        value: item.value,
      }
    })
    // 旧的types
    const oldTypes = feeTabs.value
    // 比较新旧tabs的变化
    const hasChanged = JSON.stringify(newTabs) !== JSON.stringify(oldTypes)
    // 发生了变化
    if (hasChanged) {
      const oldValues = new Set(oldTypes.map((item) => item.value))
      const newValues = new Set(newTabs.map((item) => item.value))
      // 减少的类型
      const removedValues = [...oldValues].filter((value) => !newValues.has(value))
      // 遍历减少的类型，将对应的数据集合清空
      if (removedValues.length > 0) {
        removedValues.forEach((item) => {
          if (item == 0) {
            // 清空数组
            orderFeeList.value = []
            // 重置全选|半选
            rentalChecked.value = false
            rentalIndeterminate.value = false
            emitData()
          }
          if (item == 1) {
            violationFeeList.value = []
            // 重置全选|半选
            violationChecked.value = false
            violationIndeterminate.value = false
            emitData()
          }
        })
      }
      // 更新 feeIndex
      if (feeTabIndex.value == -1 || oldTypes.length == 0) {
        feeTabIndex.value = 0
      } else {
        // 获取旧的 feeTabIndex 对应的 value
        const oldType = oldTypes[feeTabIndex.value]
        const oldTypeValue = oldType.value
        const newIndex = newTabs.findIndex((item) => item.value == oldTypeValue)
        if (newIndex != -1) {
          feeTabIndex.value = newIndex
        } else {
          feeTabIndex.value = 0
        }
      }
    }
    return {
      hasChanged,
      newTabs,
    }
  }

  /**
   * 租车费用选中
   */
  const onRentalCheckChange = () => {
    // 费用列表
    const orderList = orderFeeList.value
    // 获取选中的订单
    const checkedFeeList = orderList.filter((item) => item.check || item.indeterminate)
    // 重置选中状态
    rentalChecked.value = false
    rentalIndeterminate.value = false
    // 全部选中
    if (checkedFeeList.length > 0) {
      if (checkedFeeList.length == orderList.length) {
        rentalChecked.value = true
      } else {
        rentalIndeterminate.value = true
      }
    }

    emitData()
  }
  /**
   * 违章费用选中
   */
  const onViolationListCheckChange = () => {
    // 费用列表
    const orderList = violationFeeList.value
    // 获取选中的订单
    const checkedFeeList = orderList.filter((item) => item.check || item.indeterminate)
    // 重置选中状态
    violationChecked.value = false
    violationIndeterminate.value = false
    // 全部选中
    if (checkedFeeList.length > 0) {
      if (checkedFeeList.length == orderList.length) {
        violationChecked.value = true
      } else {
        violationIndeterminate.value = true
      }
    }

    emitData()
  }
  // 全选按钮发生改变
  const onAllCheckedChange = (type, isEmitData = true) => {
    // 租车费用
    if (currSelTabVal.value == 0 || type == 'rental') {
      // 选中状态
      const isCheck = rentalChecked.value
      orderFeeList.value.forEach((order) => {
        order.check = isCheck
        order.indeterminate = false
        // 计算选中的费项金额
        let amount = 0
        order.feeDetailList.forEach((fee) => {
          fee.check = isCheck
          fee.indeterminate = false
          amount = decimalAddition(amount, fee.realAmount)
        })
        order.checkedAmount = amount
      })
    }
    // 违章费用
    if (currSelTabVal.value == 1 || type == 'violation') {
      // 选中状态
      const isCheck = violationChecked.value
      // 违章费用
      violationFeeList.value.forEach((violation) => {
        violation.check = isCheck
        violation.indeterminate = false
      })
    }

    isEmitData && emitData()
  }

  // 全部的租车费
  const orderFeeList = ref([])
  // 全部的违章费
  const violationFeeList = ref([])
  /**
   * @description: 获取租车费用|违章费用列表
   */
  const fetchData = () => {
    const param = {
      depositId: props.depositDetail.id,
      pageNumber: 1,
      pageSize: 1000,
    }
    if (currSelTabVal.value == 0) {
      if (!orderFeeList.value.length) {
        getOrderFeeList(param).then((res) => {
          const result = res.result
          const list = result.data
          if (list && list.length > 0) {
            // costType 10 收款 20 付款
            list.forEach((order) => {
              const feeDetailList = order.feeDetailList
              if (feeDetailList && feeDetailList.length > 0) {
                feeDetailList.forEach((feeItem) => {
                  const amount = feeItem.waitPayAmount
                  // 收支类型
                  const costType = feeItem.costType
                  if (costType == 20) {
                    // 转为负值
                    feeItem.realAmount = amount == 0 ? 0 : -amount
                  } else {
                    feeItem.realAmount = amount
                  }
                })
              }
            })
          }
          orderFeeList.value = list

          emitData()
        })
      }
    }
    if (currSelTabVal.value == 1) {
      if (!violationFeeList.value.length) {
        getViolationFeeList(param).then((res) => {
          const result = res.result
          violationFeeList.value = result.data

          emitData()
        })
      }
    }
  }
  /**
   * @description: 处理费用类型变化
   * @param {Array} options
   * @return {*}
   */
  const handleTypeChange = (options) => {
    if (options && options.length > 0) {
      // 判断是否发生了变化
      const compare = compareType(options)
      if (compare.hasChanged) {
        feeTabs.value = []
        setTimeout(() => {
          // 更新 feeTabs
          feeTabs.value = compare.newTabs
          // 获取列表数据
          fetchData()
          // 发送数据
          emitData()
        }, 20)
      }
    } else {
      // 未选择费用类型
      // 更新 feeTabs
      feeTabs.value = []
      // 清空数组
      orderFeeList.value = []
      // 重置全选|半选
      rentalChecked.value = false
      rentalIndeterminate.value = false
      violationFeeList.value = []
      // 重置全选|半选
      violationChecked.value = false
      violationIndeterminate.value = false
      // 发送数据
      emitData()
    }
  }
  // 操作记录
  let recordedOperation = null
  // 回退操作
  const fallbackAction = () => {
    if (currSelTabVal.value == 0) {
      if (recordedOperation) {
        orderFeeList.value = JSON.parse(recordedOperation)
      } else {
        // 全部未选中
        orderFeeList.value.forEach((order) => {
          order.check = false
          order.indeterminate = false
          order.feeDetailList.forEach((feeItem) => {
            feeItem.check = false
          })
        })
      }

      // 更新全部选中
      onRentalCheckChange()
    }
    // 违章费用
    if (currSelTabVal.value == 1) {
      if (recordedOperation) {
        violationFeeList.value = JSON.parse(recordedOperation)
      } else {
        // 全部未选中
        violationFeeList.value.forEach((violation) => {
          violation.check = false
        })
      }

      // 更新全部选中
      onViolationListCheckChange()
    }
  }
  // 记录操作
  const recordAction = () => {
    // 租车费用
    if (currSelTabVal.value == 0) {
      recordedOperation = JSON.stringify(orderFeeList.value)
    }
    // 违章费用
    if (currSelTabVal.value == 1) {
      recordedOperation = JSON.stringify(violationFeeList.value)
    }
  }
  /**
   * @description: 发送数据
   */
  const emitData = (type = 'all') => {
    // 租车费
    if (type == 'orderFee' || type == 'all') {
      // 计算选中的结果
      const list = orderFeeList.value
      if (list.length > 0) {
        const checkedOrderFee = []
        list.forEach((order) => {
          if (order.check || order.indeterminate) {
            order.feeDetailList.forEach((fee) => {
              if (fee.check) {
                checkedOrderFee.push({
                  orderId: order.orderId,
                  orderCode: order.orderCode,
                  feeDetailId: fee.id,
                  cutPaymentAmount: fee.waitPayAmount,
                  realAmount: fee.realAmount,
                })
              }
            })
          }
        })
        emits('update:orderFeeList', checkedOrderFee)
      } else {
        emits('update:orderFeeList', [])
      }
    }
    // 违章费
    if (type == 'violationFee' || type == 'all') {
      // 计算选中的结果
      const list = violationFeeList.value
      if (list.length > 0) {
        const checkedViolationFee = []
        list.forEach((violation) => {
          if (violation.check) {
            checkedViolationFee.push({
              feeDetailId: violation.id,
              violationCode: violation.businesCode,
              cutPaymentAmount: violation.outstandingAmount,
            })
          }
        })
        emits('update:violationFeeList', checkedViolationFee)
      } else {
        emits('update:violationFeeList', [])
      }
    }

    // 当前的汇总金额
    nextTick(() => {
      const sum = props.deductionSum
      const availableAmount = props.depositDetail.availableDepositAmount
      if (sum > availableAmount) {
        uni.showToast({
          title: '剩余可操作金额不足',
          icon: 'none',
        })

        // 回退操作
        fallbackAction()
      } else {
        // 记录操作
        recordAction()
      }
    })

    emits('change')
  }

  defineExpose({
    handleTypeChange,
  })
</script>
<style lang="less" scoped>
  .fee-info {
    margin-bottom: 24rpx;
    .fee-info-header {
      background: #ffffff;
      padding: 24rpx;
      display: flex;
      align-items: center;
      justify-content: space-between;
    }
    .fee-info-content {
      padding: 24rpx;
    }
  }
  .check-box {
    padding: 0 32rpx;
    background: #3072f6;
    border-radius: 4rpx 4rpx 4rpx 4rpx;
    font-size: 28rpx;
    color: #ffffff;
    cursor: pointer;
    display: flex;
    align-items: center;
    height: 64rpx;
    line-height: 64rpx;
    margin-left: 16rpx;
    /deep/ image {
      margin-right: 16rpx;
    }
  }
</style>
